package com.corpgovernment.travelstandard.controller;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.Optional;

import com.corpgovernment.organization.constant.OrganizationResponseCodeEnum;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import com.corpgovernment.api.organization.model.post.PostVo;
import com.corpgovernment.api.organization.utils.CommonUtil;
import com.corpgovernment.api.travelstandard.enums.ControlTypeEnum;
import com.corpgovernment.api.travelstandard.enums.TrainSwitchEnum;
import com.corpgovernment.api.travelstandard.enums.TravelStandardTypeEnum;
import com.corpgovernment.api.travelstandard.vo.*;
import com.corpgovernment.api.travelstandard.vo.response.TrainTravelStandardShowTextResponse;
import com.corpgovernment.common.base.BaseUserInfo;
import com.corpgovernment.common.base.JSONResult;
import com.corpgovernment.common.common.CorpBusinessException;
import com.corpgovernment.common.enums.ExceptionCodeEnum;
import com.corpgovernment.organization.constant.OrganizationResponseCodeEnum;
import com.corpgovernment.organization.service.IPostService;
import com.corpgovernment.travelstandard.entity.db.TravelStandardPost;
import com.corpgovernment.travelstandard.impl.MbTravelstandReasonCodeService;
import com.corpgovernment.travelstandard.impl.MbTravelstandTrainSeatService;
import com.corpgovernment.travelstandard.impl.MbTravelstandTrainService;
import com.corpgovernment.travelstandard.impl.TravelStandardPostService;
import com.corpgovernment.travelstandard.utils.BeanConverUtil;
import com.ctrip.corp.obt.generic.utils.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import java.util.*;

/**
 * 国内机票
 */
@RestController
@RequestMapping("trainTravelStandardManage")
public class TrainTravelStandardManageController {

    private final static String TRAIN_TRAVEL_STANDARD_DEFAULT_NAME = "火车票差旅标准";

    @Autowired
    private TravelStandardPostService standPostService;
    @Autowired
    private IPostService postService;
    @Autowired
    private MbTravelstandTrainService travelstandTrainService;
    @Autowired
    private MbTravelstandReasonCodeService travelstandReasonCodeService;
    @Autowired
    private MbTravelstandTrainSeatService travelstandTrainSeatService;

    /**
     * 新增
     * @return
     */
    @RequestMapping("toAdd")
    public JSONResult toAddTrainTravelStand(@RequestBody TrainTravelStandardManageVo trainTravelStandardManageVo) {
        String title = trainTravelStandardManageVo.getTitle();
        if (StringUtils.isBlank(title)) {
            title = TRAIN_TRAVEL_STANDARD_DEFAULT_NAME;
        }
        String orgId = trainTravelStandardManageVo.getOrgId();
        if (StringUtils.isBlank(orgId)) {
            throw new CorpBusinessException(OrganizationResponseCodeEnum.ORG_ID_NULL);
        }
        MbTravelstandTrainVo travelstandTrainVo = new MbTravelstandTrainVo(
                null,
                orgId,
                title,
                TrainSwitchEnum.seatSwitch.N.getCode(),
                ControlTypeEnum.F.getCode(),
                TrainSwitchEnum.seatSwitch.N.getCode(),
                ControlTypeEnum.F.getCode(),
                TrainSwitchEnum.seatSwitch.N.getCode());
        travelstandTrainVo.setProductSwitch("E");
        travelstandTrainService.insertTravelstandTrain(travelstandTrainVo);
        // 对应RC
        List<MbTravelstandReasonCodeVo> travelstandReasonCodeVos =
                travelstandReasonCodeService.list(new MbTravelstandReasonCodeVo() {
                    {
                        setTsId(travelstandTrainVo.getId());
                        setTsType(TravelStandardTypeEnum.Train.getCode());
                    }
                });
        // 获取相关坐席
        List<MbTravelstandTrainSeatVo> travelstandTrainSeatVos =
                travelstandTrainSeatService.list(new MbTravelstandTrainSeatVo() {
                    {
                        setTsTrainId(travelstandTrainVo.getId());
                    }
                });
        Map<String, Object> returnMap = new HashMap<>();
        returnMap.put("trainControl", BeanConverUtil.travelstandTrainVoToTrainTravelStandardManageVo(travelstandTrainVo,
                new ArrayList<>(), travelstandReasonCodeVos, travelstandTrainSeatVos));
        return JSONResult.success(returnMap);
    }

    /**
     * 更新差标属性
     * @param vo
     * @return
     */
    @RequestMapping("save")
    public JSONResult addTrainTravelStand(@RequestBody TrainTravelStandardManageVo vo) {
        return travelstandTrainService.updateTravelStandardTrainProperty(vo);
    }

    /**
     * 更新差标名称
     */
    @RequestMapping("updateStandardName")
    public JSONResult updateStandardName(@RequestBody TrainTravelStandardManageVo trainTravelStandardManageVo) {
        String id = trainTravelStandardManageVo.getId();
        if (StringUtils.isBlank(id)) {
            throw new CorpBusinessException(OrganizationResponseCodeEnum.PARAMS_IS_NULL, "id");
        }
        String title = trainTravelStandardManageVo.getTitle();
        if (StringUtils.isBlank(title)) {
            throw new CorpBusinessException(OrganizationResponseCodeEnum.PARAMS_IS_NULL, "title");
        }
        travelstandTrainService.updateStandardName(Long.valueOf(id), title);
        return JSONResult.ok();
    }

    /**
     * 删除差标
     * @return
     */
    @RequestMapping("delete")
    public JSONResult deleteTrainTravelStand(@RequestBody TrainTravelStandardManageVo trainTravelStandardManageVo) {
        String id = trainTravelStandardManageVo.getId();
        if (StringUtils.isBlank(id)) {
            throw new CorpBusinessException(OrganizationResponseCodeEnum.PARAMS_IS_NULL, "id");
        }
        return travelstandTrainService.deleteTravelstandTrain(Long.parseLong(id));
    }

    /**
     * 获取差标
     */
    @RequestMapping("get")
    public JSONResult getTrainTravelStand(@RequestBody TrainTravelStandardManageVo trainTravelStandardManageVo) {
        String orgId = trainTravelStandardManageVo.getOrgId();
        if (StringUtils.isBlank(orgId)) {
            throw new CorpBusinessException(OrganizationResponseCodeEnum.ORG_ID_NULL);
        }
        // 获取全部岗位
        List<PostVo> posts = postService.listPostByOrgId(orgId);
        // 已选职位
        List<TravelStandardPostVo> travelStandardPostVos =
                standPostService.selectByTsTypeAndOrgId(TravelStandardTypeEnum.Train.getCode(), orgId);
        List<Long> jobScope = new ArrayList<>();
        for (TravelStandardPostVo travelStandardPostVo : travelStandardPostVos) {
            jobScope.add(travelStandardPostVo.getPostid());
        }
        // 该组织下下所有火车票差标
        List<TrainTravelStandardManageVo> domAirTicket =
                travelstandTrainService.listTravelstandTrain(new MbTravelstandTrainVo() {
                    {
                        setOrgId(orgId);
                    }
                });
        Map<String, Object> returnMap = new HashMap<>();
        returnMap.put("trainControl", domAirTicket);
        returnMap.put("jobScopeSelectList", jobScope);
        returnMap.put("jobScopeAllList", posts);

        return JSONResult.success(returnMap);
    }

    /**
     * 更新rc
     * @param rcListVo
     * @return
     */
    @RequestMapping("updateRc")
    public JSONResult updateRc(@RequestBody RCListVo rcListVo) {
        rcListVo.setTsType(TravelStandardTypeEnum.Train.getCode());
        travelstandReasonCodeService.updateTravelstandReasonCode(rcListVo);
        return JSONResult.ok();
    }

    /**
     * SOA-根据uid、orgId/tsId查询火车票差标
     */
    @RequestMapping("getTrainTravelStandard")
    public JSONResult<TrainTravelStandardSoaVo>
            getTrainTravelStandard(@RequestBody TravelStandardSoaRequestVo travelStandardSoaRequestVo) {
        TrainTravelStandardSoaVo travelStandard = null;
        if (Objects.nonNull(travelStandardSoaRequestVo.getTrafficId())) {
            travelStandard =
                    travelstandTrainService.getTrainTravelStandard(travelStandardSoaRequestVo.getTrafficId());
        }

        if (Objects.nonNull(travelStandard)) {
            return JSONResult.success(travelStandard);
        }

        Long tsId;
        if (!StringUtils.isBlank(travelStandardSoaRequestVo.getTsId())) {
            tsId = Long.valueOf(travelStandardSoaRequestVo.getTsId());
        } else {
            Long postId = null;
            if (Objects.nonNull(travelStandardSoaRequestVo.getPostId()) && travelStandardSoaRequestVo.getPostId() > 0) {
                postId = travelStandardSoaRequestVo.getPostId();
            } else {
                String uid = travelStandardSoaRequestVo.getUserId();
                String corpId = travelStandardSoaRequestVo.getOrgId();
                if (StringUtils.isBlank(uid)) {
                    return JSONResult.errorMsg("用户id不能为空");
                }
                if (StringUtils.isBlank(corpId)) {
                    return JSONResult.errorMsg("公司id不能为空");
                }
                PostVo postVo = postService.listPostByUidAndOrgId(uid, corpId);
                // 判断岗位是否存在
                if (postVo == null) {
                    return JSONResult.ok();
                }
                postId = postVo.getId();
            }

            TravelStandardPostVo vo = new TravelStandardPostVo();
            vo.setPostid(postId);
            vo.setTstype(TravelStandardTypeEnum.Train.getCode());
            List<TravelStandardPost> travelStandardPostVos = standPostService.list(vo);
            // 判断该岗位下是否关联了差标
            if (travelStandardPostVos == null || travelStandardPostVos.size() == 0) {
                return JSONResult.ok();
            }
            TravelStandardPost travelStandardPost = travelStandardPostVos.get(0);
            tsId = travelStandardPost.getTsid();
        }
        MbTravelstandTrainVo travelstandTrainVo = travelstandTrainService.get(tsId);
        // 判断该差标是否存在
        if (travelstandTrainVo == null) {
            return JSONResult.ok();
        }
        // 获取差标rc
        List<MbTravelstandReasonCodeVo> travelstandReasonCodeVos = travelstandReasonCodeService.list(
                new MbTravelstandReasonCodeVo()
                        .setTsId(travelstandTrainVo.getId())
                        .setTsType(TravelStandardTypeEnum.Train.getCode()));
        // 获取已选坐席
        List<MbTravelstandTrainSeatVo> travelstandTrainSeatVos =
                travelstandTrainSeatService.list(new MbTravelstandTrainSeatVo() {
                    {
                        setTsTrainId(travelstandTrainVo.getId());
                    }
                });
        // 获取相关职位
        List<TravelStandardPost> travelStandardPosts = standPostService.list(new TravelStandardPostVo() {
            {
                setTsid(travelstandTrainVo.getId());
            }
        });
        TrainTravelStandardSoaVo trainTravelStandardSoaVo = BeanConverUtil.travelstandTrainVoToTrainTravelStandardSoaVo(
                travelstandTrainVo,
                CommonUtil.copyList(travelStandardPosts, TravelStandardPostVo.class),
                travelstandReasonCodeVos,
                travelstandTrainSeatVos);
        return JSONResult.success(trainTravelStandardSoaVo);
    }

    /**
     * APP-火车票差标展示
     */
    @RequestMapping("trainTravelStandardShowApp")
    public JSONResult<TrainTravelStandardShowVo> trainTravelStandardShowApp(
            @RequestBody(required = false) TravelStandardAppRequestVo travelStandardAppRequestVo,
            BaseUserInfo baseUserInfo) {
        String orgId;
        String uid;
        Long postId = null;
        Long trafficId = null;


        if (travelStandardAppRequestVo == null) {
            orgId = baseUserInfo.getOrgId();
            uid = baseUserInfo.getUid();
        } else {
            orgId = travelStandardAppRequestVo.getOrgId();
            uid = travelStandardAppRequestVo.getUid();
            trafficId = travelStandardAppRequestVo.getTrafficId();
            if (StringUtils.isBlank(orgId) && StringUtils.isBlank(uid)) {
                orgId = baseUserInfo.getOrgId();
                uid = baseUserInfo.getUid();
            }
            if (Objects.nonNull(travelStandardAppRequestVo.getPostId()) && travelStandardAppRequestVo.getPostId() > 0) {
                postId = travelStandardAppRequestVo.getPostId();
            }

        }
        return travelstandTrainService.trainTravelStandardShowApp(orgId, uid, postId, trafficId, travelStandardAppRequestVo.getToken());
    }

    /**
     * SOA-火车票差标展示
     */
    @RequestMapping("trainTravelStandardShowSoa")
    public JSONResult<TrainTravelStandardShowSoaVo>
            trainTravelStandardShowSoa(@RequestBody TravelStandardSoaRequestVo travelStandardSoaRequestVo) {
        TrainTravelStandardShowSoaVo travelStandard = null;
        if (Objects.nonNull(travelStandardSoaRequestVo.getTrafficId())) {
            travelStandard =
                    travelstandTrainService.trainTravelStandardShowSoa(travelStandardSoaRequestVo.getTrafficId());
        }

        if (Objects.nonNull(travelStandard)) {
            return JSONResult.success(travelStandard);
        }
        return travelstandTrainService.trainTravelStandardShowSoa(travelStandardSoaRequestVo);
    }

    /**
     * SOA-文本展示个人火车票差标
     *
     * @return
     */
    @RequestMapping("trainTravelStandardShowText")
    public JSONResult<TrainTravelStandardShowTextResponse>
            trainTravelStandardShowText(@RequestBody TravelStandardSoaRequestVo travelStandardSoaRequestVo) {
        TrainTravelStandardShowTextResponse travelStandard = null;
        if (Optional.ofNullable(travelStandardSoaRequestVo)
                .map(TravelStandardSoaRequestVo::getTrafficId)
                .isPresent()) {
            travelStandard =
                    travelstandTrainService.trainTravelStandardShowText(travelStandardSoaRequestVo.getTrafficId());
        }

        if (Objects.nonNull(travelStandard)) {
            return JSONResult.success(travelStandard);
        }

        return travelstandTrainService.trainTravelStandardShowText(travelStandardSoaRequestVo.getUserId(),
                travelStandardSoaRequestVo.getOrgId());
    }

}
